package org.ssi.web.util;

import java.awt.Image;
import java.awt.image.BufferedImage;
import java.awt.image.ImageProducer;
import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;

import javax.imageio.ImageIO;

import org.apache.commons.lang.StringUtils;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;

import com.sun.image.codec.jpeg.JPEGCodec;
import com.sun.image.codec.jpeg.JPEGImageEncoder;
import com.sun.jimi.core.Jimi;
import com.sun.jimi.core.JimiException;
import com.sun.jimi.core.JimiWriter;
import com.sun.jimi.core.options.JPGOptions;

/**
 * @author 
 */
public class ImageUtils {

	private static final Log log = LogFactory.getLog(ImageUtils.class);

	/**
	 * ����Ŀ¼
	 * 
	 * @param directory
	 * @return true if no error occured
	 * @throws FileNotFoundException
	 * @throws IOException
	 */
	public static boolean ergodDirectory(String directory) throws FileNotFoundException, IOException {
		try {
			File file = new File(directory);
			if (file.isDirectory()) {
				String[] fileList = file.list();
				for (int i = 0; i < fileList.length; i++) {
					File readfile = new File(directory + File.pathSeparator + fileList[i]);
					if (!readfile.isDirectory()) {
						// ImageUtils.resizeByMaxSize(readfile.getAbsolutePath(),
						// null, new int[] { 60, 120, 200, 400
						// });
					} else if (readfile.isDirectory()) {
						ergodDirectory(directory + File.pathSeparator + fileList[i]);
					}
				}
			}
		} catch (FileNotFoundException e) {
			System.err.println("FileNotFound");
		}
		return true;
	}

	public static void main(String[] args) {
		try {
			// ImageUtils.ergodDirectory("G:\\Temp\\My Documents\\My
			// Pictures\\test");
			ImageUtils.resizeByMaxSize("G:\\Temp\\My Documents\\My Pictures\\test\\girl.jpg", "", 200);
			ImageUtils.resizeByMaxSize("G:\\Temp\\My Documents\\My Pictures\\test\\msn.bmp", "", 200);
			ImageUtils.resizeByMaxSize("G:\\Temp\\My Documents\\My Pictures\\test\\rb.gif", "", 200);
			ImageUtils.resizeByMaxSize("G:\\Temp\\My Documents\\My Pictures\\test\\xm.gif", "", 200);

			ImageUtils.resizeByFixedWidth("G:\\Temp\\My Documents\\My Pictures\\test\\girl.jpg", "", 200);
			ImageUtils.resizeByFixedWidth("G:\\Temp\\My Documents\\My Pictures\\test\\msn.bmp", "", 200);
			ImageUtils.resizeByFixedWidth("G:\\Temp\\My Documents\\My Pictures\\test\\rb.gif", "", 200);
			ImageUtils.resizeByFixedWidth("G:\\Temp\\My Documents\\My Pictures\\test\\xm.gif", "", 200);
		} catch (Exception ex) {
			ex.printStackTrace();
		}
	}

	/**
	 * ָ��Ŀ¼λ�����ָ����Ⱥ͸߶ȵ�ͼƬ,�뱣֤ԴͼƬ�ļ�Ϊ JPG ��ʽ
	 * 
	 * @param source ԴͼƬ����·��
	 * @param desc Ŀ¼ͼƬ����·��
	 * @param width ���ͼƬ�Ŀ��
	 * @param height ���ͼƬ�ĸ߶�
	 * @throws IOException
	 * @author 
	 */
	public static void resize(String source, String desc, int width, int height) throws IOException {
		Image sourceImage = ImageIO.read(new File(source));
		BufferedImage bi = new BufferedImage(width, height, BufferedImage.TYPE_INT_RGB);
		bi.getGraphics().drawImage(sourceImage.getScaledInstance(width, height, Image.SCALE_SMOOTH), 0, 0, null);

		FileOutputStream out = new FileOutputStream(desc);
		JPEGImageEncoder encoder = JPEGCodec.createJPEGEncoder(out);
		encoder.encode(bi);
		out.close();
	}

	/**
	 * ��ݹ̶�������ͼƬ
	 * 
	 * @param source ԴͼƬ����·��
	 * @param desc Ŀ¼ͼƬ����·�������Ϊ�գ�������ʽΪ:ԴͼƬ��Ʋ�����չ���_'h'fixedWidth.��չ��
	 * @param fixedHeight �̶��ĸ߶�
	 * @throws JimiException
	 * @throws IOException
	 * @author 
	 */
	public static void resizeByFixedHeight(String source, String desc, int fixedHeight) throws JimiException,
			IOException {
		if (StringUtils.isBlank(desc)) {
			desc = StringUtils.substringBeforeLast(source, "_") + "_"
					+ StringUtils.leftPad(String.valueOf(fixedHeight), 3, "0") + ".jpg";
		}
		if (log.isDebugEnabled()) {
			log.debug("source image file:" + source);
		}
		if (log.isDebugEnabled()) {
			log.debug("desc image file:" + desc);
		}
		String jpgSource = toJPG(source, null, 100);

		if (log.isDebugEnabled()) {
			log.debug("source jpg file:" + jpgSource);
		}

		Image sourceImage = ImageIO.read(new File(jpgSource));

		double sourceImageWidth = sourceImage.getWidth(null);
		double sourceImageHeight = sourceImage.getHeight(null);

		int resizedWidth = (int) ((sourceImageWidth / sourceImageHeight) * fixedHeight);

		ImageUtils.resize(jpgSource, desc, resizedWidth, fixedHeight);

	}

	/**
	 * ��ݹ̶�������ͼƬ
	 * 
	 * @param source ԴͼƬ����·��
	 * @param desc Ŀ¼ͼƬ����·�������Ϊ�գ�������ʽΪ:ԴͼƬ��Ʋ�����չ���_'w'fixedWidth.��չ��
	 * @param fixedWidth �̶��Ŀ��
	 * @throws JimiException
	 * @throws IOException
	 * @author 
	 */
	public static void resizeByFixedWidth(String source, String desc, int fixedWidth) throws JimiException, IOException {
		if (StringUtils.isBlank(desc)) {
			desc = StringUtils.substringBeforeLast(source, "_") + "_"
					+ StringUtils.leftPad(String.valueOf(fixedWidth), 3, "0") + ".jpg";
		}
		if (log.isDebugEnabled()) {
			log.debug("source image file:" + source);
		}
		if (log.isDebugEnabled()) {
			log.debug("desc image file:" + desc);
		}
		String jpgSource = toJPG(source, null, 100);

		if (log.isDebugEnabled()) {
			log.debug("source jpg file:" + jpgSource);
		}
		Image sourceImage = ImageIO.read(new File(jpgSource));

		double sourceImageWidth = sourceImage.getWidth(null);
		double sourceImageHeight = sourceImage.getHeight(null);

		int resizedHeight = (int) ((sourceImageHeight / sourceImageWidth) * fixedWidth);

		ImageUtils.resize(jpgSource, desc, fixedWidth, resizedHeight);
	}

	/**
	 * �����������ͼƬ
	 * 
	 * @param source ԴͼƬ����·��
	 * @param desc Ŀ¼ͼƬ����·�������Ϊ�գ�������ʽΪ:ԴͼƬ��Ʋ�����չ���_maxSize.��չ��
	 * @param maxSize
	 * @throws JimiException
	 * @throws IOException
	 * @author 
	 */
	public static void resizeByMaxSize(String source, String desc, int maxSize) throws JimiException, IOException {
		if (StringUtils.isBlank(desc)) {
			desc = StringUtils.substringBeforeLast(source, ".") + "_"
					+ StringUtils.leftPad(String.valueOf(maxSize), 3, "0") + ".jpg";
		}
		if (log.isDebugEnabled()) {
			log.debug("source image file:" + source);
		}
		if (log.isDebugEnabled()) {
			log.debug("desc image file:" + desc);
		}
		String jpgSource = toJPG(source, null, 100);

		if (log.isDebugEnabled()) {
			log.debug("source jpg file:" + jpgSource);
		}
		double ratio = 0.0d;

		Image sourceImage = ImageIO.read(new File(jpgSource));

		double sourceImageWidth = sourceImage.getWidth(null);
		double sourceImageHeight = sourceImage.getHeight(null);

		if (sourceImageHeight > sourceImageWidth) {
			ratio = maxSize / sourceImageHeight;
		} else {
			ratio = maxSize / sourceImageWidth;
		}

		int resizedWidth = (int) (sourceImageWidth * ratio);
		int resizedHeight = (int) (sourceImageHeight * ratio);

		ImageUtils.resize(jpgSource, desc, resizedWidth, resizedHeight);
	}

	/**
	 * ������ű�������ͼƬ
	 * 
	 * @param source ԴͼƬ����·��
	 * @param desc Ŀ¼ͼƬ����·�������Ϊ�գ�������ʽΪ:ԴͼƬ��Ʋ�����չ���_'r'ratio * 100.��չ��
	 * @param ratio ���ű���
	 * @throws JimiException
	 * @throws IOException
	 * @author 
	 */
	public static void resizeByRatio(String source, String desc, double ratio) throws JimiException, IOException {
		if (StringUtils.isBlank(desc)) {
			desc = StringUtils.substringBeforeLast(source, ".") + "_"
					+ StringUtils.leftPad(String.valueOf((ratio * 100)), 3, "0") + ".jpg";
		}
		if (log.isDebugEnabled()) {
			log.debug("source image file:" + source);
		}
		if (log.isDebugEnabled()) {
			log.debug("desc image file:" + desc);
		}
		String jpgSource = toJPG(source, null, 100);

		if (log.isDebugEnabled()) {
			log.debug("source jpg file:" + jpgSource);
		}

		String jpgSourceFile = toJPG(source, null, 100);
		Image sourceImage = ImageIO.read(new File(jpgSource));

		double sourceImageWidth = sourceImage.getWidth(null);
		double sourceImageHeight = sourceImage.getHeight(null);

		int resizedWidth = (int) (sourceImageWidth * ratio);
		int resizedHeight = (int) (sourceImageHeight * ratio);

		ImageUtils.resize(jpgSourceFile, desc, resizedWidth, resizedHeight);
	}

	/**
	 * ��ͼƬת�� JPG ��ʽ������Ѿ���JPG��ʽ����ת������Ҫ JimiProClasses.jar ֧��
	 * 
	 * @param source ԴͼƬ�ļ�����·��
	 * @param dest Ŀ��ͼƬ�ļ�����·�������Դ�ļ����� JPG ��׺����ɵ� jpg �ļ����ļ���Ϊ��ԭ�����ļ��� + .jpg
	 * @param quality ���ͼƬ��������0(���)-75(�Ϻã�Ĭ��)-100(���)}
	 * @return ת�����ͼƬ����·��
	 * @throws JimiException
	 * @author 
	 */
	public static String toJPG(String source, String dest, int quality) throws JimiException {
		if ((dest == null) || dest.trim().equals("")) {
			dest = source;
		}
		if (!dest.toLowerCase().trim().endsWith(".jpg")) {
			dest += ".jpg";

			if ((quality < 0) || (quality > 100) || ((quality + "") == null) || (quality + "").equals("")) {
				quality = 75;
			}
			JPGOptions options = new JPGOptions();
			options.setQuality(quality);
			ImageProducer image = Jimi.getImageProducer(source);
			JimiWriter writer = Jimi.createJimiWriter(dest);
			writer.setSource(image);
			// add options here if necessary
			writer.setOptions(options);
			writer.putImage(dest);
		}
		return dest;
	}
}
